package models

import (
	"errors"
	"time"

	"github.com/beego/beego/v2/client/orm"
	"golang.org/x/crypto/bcrypt"
)

// Admin 管理员模型
type Admin struct {
	BaseModel
	Username    string `orm:"size(64);unique" json:"username"`
	Password    string `orm:"size(128)" json:"-"`
	RealName    string `orm:"size(64)" json:"real_name"`
	Mobile      string `orm:"size(20)" json:"mobile"`
	Email       string `orm:"size(100)" json:"email"`
	Avatar      string `orm:"size(255)" json:"avatar"`
	Status      int8   `orm:"default(1)" json:"status"` // 1:正常, 0:禁用
	LastLoginAt int64  `orm:"" json:"last_login_at"`
	LastLoginIp string `orm:"size(50)" json:"last_login_ip"`
	RoleId      int64  `orm:"default(0)" json:"role_id"`
}

// IsSuper 判断是否为超级管理员
func (a *Admin) IsSuper() bool {
	return a.FranchiseId == 0
}

// TableName 设置表名
func (a *Admin) TableName() string {
	return "ss_admin"
}

// SetPassword 设置密码，使用bcrypt加密
func (a *Admin) SetPassword(password string) error {
	if len(password) == 0 {
		return errors.New("密码不能为空")
	}

	hashedPassword, err := bcrypt.GenerateFromPassword([]byte(password), bcrypt.DefaultCost)
	if err != nil {
		return err
	}

	a.Password = string(hashedPassword)
	return nil
}

// CheckPassword 验证密码
func (a *Admin) CheckPassword(password string) bool {
	err := bcrypt.CompareHashAndPassword([]byte(a.Password), []byte(password))
	return err == nil
}

// UpdateLoginInfo 更新登录信息
func (a *Admin) UpdateLoginInfo(ip string) error {
	a.LastLoginAt = time.Now().Unix()
	a.LastLoginIp = ip

	o := orm.NewOrm()
	_, err := o.Update(a, "LastLoginAt", "LastLoginIp")
	return err
}

// GetAdminById 根据ID获取管理员信息
func GetAdminById(id int64) (*Admin, error) {
	admin := &Admin{BaseModel: BaseModel{Id: id}}
	o := orm.NewOrm()
	err := o.Read(admin)
	if err != nil {
		return nil, err
	}

	return admin, nil
}

// GetAdminByUsername 根据用户名获取管理员信息
func GetAdminByUsername(username string) (*Admin, error) {
	admin := &Admin{Username: username}
	o := orm.NewOrm()
	err := o.Read(admin, "username")
	if err != nil {
		return nil, err
	}

	return admin, nil
}

// GetAdminList 获取管理员列表
func GetAdminList(page, pageSize int, filters map[string]interface{}) ([]*Admin, int64, error) {
	o := orm.NewOrm()
	qs := o.QueryTable(new(Admin))

	// 应用过滤条件
	if franchiseId, ok := filters["franchise_id"].(int64); ok {
		qs = qs.Filter("franchise_id", franchiseId)
	}

	if username, ok := filters["username"].(string); ok && username != "" {
		qs = qs.Filter("username__contains", username)
	}

	if realName, ok := filters["real_name"].(string); ok && realName != "" {
		qs = qs.Filter("real_name__contains", realName)
	}

	if status, ok := filters["status"].(int8); ok {
		qs = qs.Filter("status", status)
	}

	// 排除已删除的记录
	qs = qs.Filter("is_deleted", 0)

	// 获取总数
	total, _ := qs.Count()

	// 分页查询
	var admins []*Admin
	_, err := qs.OrderBy("-id").Limit(pageSize, (page-1)*pageSize).All(&admins)

	return admins, total, err
}

// CreateAdmin 创建管理员
func CreateAdmin(admin *Admin) (int64, error) {
	o := orm.NewOrm()
	id, err := o.Insert(admin)
	return id, err
}

// UpdateAdmin 更新管理员信息
func UpdateAdmin(admin *Admin, fields ...string) error {
	o := orm.NewOrm()
	_, err := o.Update(admin, fields...)
	return err
}

// DeleteAdmin 删除管理员（软删除）
func DeleteAdmin(id int64) error {
	o := orm.NewOrm()
	admin := &Admin{BaseModel: BaseModel{Id: id}}
	if err := o.Read(admin); err != nil {
		return err
	}

	admin.IsDeleted = 1
	_, err := o.Update(admin, "IsDeleted")
	return err
}

// GetFranchiseIdsByAdminId 根据管理员ID获取加盟商ID列表
func GetFranchiseIdsByAdminId(adminId int64) ([]int64, error) {
	admin, err := GetAdminById(adminId)
	if err != nil {
		return nil, err
	}

	// 如果是超级管理员，返回所有加盟商ID
	if admin.IsSuper() {
		o := orm.NewOrm()
		var franchises []*Franchise
		_, err := o.QueryTable(new(Franchise)).Filter("is_deleted", 0).All(&franchises)
		if err != nil {
			return nil, err
		}

		franchiseIds := make([]int64, len(franchises))
		for i, franchise := range franchises {
			franchiseIds[i] = franchise.Id
		}
		return franchiseIds, nil
	}

	// 如果不是超级管理员，只返回自己的加盟商ID
	return []int64{admin.FranchiseId}, nil
}

// InitSuperAdmin 初始化超级管理员账号
func InitSuperAdmin() error {
	// 检查是否已存在admin账号
	existAdmin, err := GetAdminByUsername("admin")
	if err == nil && existAdmin != nil {
		// 已存在admin账号，不需要创建
		return nil
	}

	// 创建超级管理员账号
	admin := &Admin{
		Username: "admin",
		RealName: "超级管理员",
		Status:   1,
	}
	admin.FranchiseId = 0 // 0表示总部

	// 设置密码
	err = admin.SetPassword("adminadmin")
	if err != nil {
		return err
	}

	// 保存管理员信息
	o := orm.NewOrm()
	_, err = o.Insert(admin)

	return err
}
